package com.fll.server.web;

import com.fll.common.container.Container;
import com.fll.server.config.ProxyConfig;
import com.fll.server.web.routes.RouteConfig;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelHandler;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelPipeline;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.codec.http.HttpObjectAggregator;
import io.netty.handler.codec.http.HttpServerCodec;
import io.netty.handler.stream.ChunkedWriteHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * @author fanlei
 * @version 1.0
 * @date 2019年01月25日
 */
public class WebConfigContainer implements Container {
    private static Logger logger = LoggerFactory.getLogger(WebConfigContainer.class);
    private NioEventLoopGroup serverWorkerGroup = new NioEventLoopGroup(1);
    private NioEventLoopGroup serverBossGroup = new NioEventLoopGroup(1);

    public WebConfigContainer() {
    }

    public void start() {
        ServerBootstrap httpServerBootstrap = new ServerBootstrap();
        ((ServerBootstrap)httpServerBootstrap.group(this.serverBossGroup, this.serverWorkerGroup).channel(NioServerSocketChannel.class)).childHandler(new ChannelInitializer<SocketChannel>() {
            public void initChannel(SocketChannel ch) throws Exception {
                ChannelPipeline pipeline = ch.pipeline();
                /** 解析Http请求 */
                pipeline.addLast(new ChannelHandler[]{new HttpServerCodec()});
                //主要是将同一个http请求或响应的多个消息对象变成一个 fullHttpRequest完整的消息对象
                pipeline.addLast(new ChannelHandler[]{new HttpObjectAggregator(65536)});
                //主要用于处理大数据流,比如一个1G大小的文件如果你直接传输肯定会撑暴jvm内存的 ,加上这个handler我们就不用考虑这个问题了
                pipeline.addLast(new ChannelHandler[]{new ChunkedWriteHandler()});
                pipeline.addLast(new ChannelHandler[]{new HttpRequestHandler()});
            }
        });

        try {
            httpServerBootstrap.bind(ProxyConfig.getInstance().getConfigServerBind(), ProxyConfig.getInstance().getConfigServerPort()).get();
            logger.info("http server start on port " + ProxyConfig.getInstance().getConfigServerPort());
        } catch (Exception var3) {
            throw new RuntimeException(var3);
        }

        RouteConfig.init();
    }

    public void stop() {
        this.serverBossGroup.shutdownGracefully();
        this.serverWorkerGroup.shutdownGracefully();
    }
}
